package com.eden.service.impl;

import java.awt.Color;
import java.awt.Font;
import java.io.File;
import java.io.IOException;
import java.util.List;
import java.util.Map;

import org.apache.commons.lang.time.DateFormatUtils;
import org.apache.commons.logging.Log;
import org.apache.commons.logging.LogFactory;
import org.jfree.chart.ChartFactory;
import org.jfree.chart.ChartUtilities;
import org.jfree.chart.JFreeChart;
import org.jfree.chart.axis.CategoryAxis;
import org.jfree.chart.axis.NumberAxis;
import org.jfree.chart.labels.StandardCategoryItemLabelGenerator;
import org.jfree.chart.plot.CategoryPlot;
import org.jfree.chart.plot.PiePlot;
import org.jfree.chart.plot.PlotOrientation;
import org.jfree.chart.renderer.category.BarRenderer;
import org.jfree.chart.renderer.category.BarRenderer3D;
import org.jfree.chart.renderer.category.CategoryItemRenderer;
import org.jfree.chart.title.TextTitle;
import org.jfree.data.category.CategoryDataset;
import org.jfree.data.general.DatasetUtilities;
import org.jfree.data.general.DefaultPieDataset;

import com.eden.config.Chart;
import com.eden.config.Configuration;
import com.eden.config.ScoreRange;
import com.eden.constant.Constant;
import com.eden.service.ChartService;
import com.eden.ui.Model;
import com.eden.util.TypeConvertUtil;

public class ChartServiceImpl extends BaseServiceImpl implements ChartService {
	private final static Log log = LogFactory.getLog(ChartServiceImpl.class) ;
	
	@SuppressWarnings("unchecked")
	public File createChart(Configuration configuration , Model model) {
		
		Map<String, Map<String , Double>> scoreDist = (Map<String, Map<String, Double>>) model.getAttrbute(Constant.SCORE_DISTRIBUTE_KEY) ;
		
		List<ScoreRange> scoreRangeList = configuration.getScoreRangeList() ;
		
		String[] rowKeys = new String[scoreDist.size()] ;
		String[] columnKeys = new String[scoreRangeList.size()] ;
		double[][] data1 = new double[rowKeys.length][columnKeys.length] ;
		
		int entryIndex = 0 ;
		for(java.util.Map.Entry<String, Map<String, Double>>  entry : scoreDist.entrySet()) {
			rowKeys[entryIndex] = entry.getKey() ;
			for(int i = 0 ,length = scoreRangeList.size(); i < length ; i++ ) {
				columnKeys[i] = scoreRangeList.get(i).getName() ;
				data1[entryIndex][i] = TypeConvertUtil.toDouble(entry.getValue().get(scoreRangeList.get(i).getName()) );
			}
			entryIndex++ ;
		}
		
		CategoryDataset dataset = DatasetUtilities.createCategoryDataset(
				rowKeys, columnKeys, data1);
		return createChart(configuration.getChart() , dataset) ;
	}
	
	public File createChart(Chart chartConfig , CategoryDataset dataset) {
		int chartType = chartConfig.getType() ;
		String chartPath = Constant.CHART_PATH + DateFormatUtils.format(System.currentTimeMillis(), "yyMMddHHmmss") + ".png";
		if (chartConfig == null)
			chartConfig = new Chart(); // 测试阶段
		
		JFreeChart chart = null ;
		if (chartType == Chart.CHART_LINE) {
			chart = createLineChart(dataset,  chartConfig);
		} else if (chartType == Chart.CHART_BAR) {
			chart = createBarChart(dataset,  chartConfig);
		} else if (chartType == Chart.CHART_BAR3D) {
			chart = createBar3DChart(dataset,  chartConfig);
		} else if (chartType == Chart.CHART_PIE) {
			chart = createPieChart(dataset,  chartConfig);
		}
		
		try {
			log.info("createChart:" + chartPath);
			File chartFile = new File(chartPath) ;
			ChartUtilities.saveChartAsPNG(chartFile , chart , 535, 290);
			return chartFile ;
		} catch (IOException e) {
			e.printStackTrace();
			log.error("create bar 3d error" , e) ;
		}
		return null ;
	}

	public JFreeChart createLineChart(CategoryDataset dataset, Chart chartConfig) {
		JFreeChart chart = null;
		chart = ChartFactory.createLineChart(chartConfig.getTitle(),
				chartConfig.getxName(), chartConfig.getyName(), dataset,
				PlotOrientation.VERTICAL, true, true, true);
		CategoryPlot categoryplot = (CategoryPlot) chart.getPlot();

		NumberAxis numberaxis = (NumberAxis) categoryplot.getRangeAxis();
		numberaxis.setStandardTickUnits(NumberAxis.createIntegerTickUnits());
		CategoryItemRenderer barrenderer = categoryplot.getRenderer();
		barrenderer.setBaseItemLabelFont(new Font("宋体", Font.PLAIN, 12));
		barrenderer.setSeriesItemLabelFont(1, new Font("宋体", Font.PLAIN, 12));
		CategoryAxis domainAxis = categoryplot.getDomainAxis();

		// 设置距离图片左端距离
		domainAxis.setLowerMargin(0.03);
		// 设置距离图片右端距离
		domainAxis.setUpperMargin(0.02);
		// 设置 columnKey 是否间隔显示
		// domainAxis.setSkipCategoryLabelsToFit(true);
		categoryplot.setDomainAxis(domainAxis);

		// 设置最高的一个 Item 与图片顶端的距离
		numberaxis.setUpperMargin(0.2);

		// 设置X轴坐标上的文字
		domainAxis.setTickLabelFont(new Font("sans-serif", Font.PLAIN, 11));

		// 设置X轴的标题文字
		domainAxis.setLabelFont(new Font("宋体", Font.PLAIN, 12));

		// 设置Y轴坐标上的文字
		numberaxis.setTickLabelFont(new Font("sans-serif", Font.PLAIN, 12));

		// 设置Y轴的标题文字
		numberaxis.setLabelFont(new Font("黑体", Font.PLAIN, 12));

		// 解决底部汉字乱码
		chart.getLegend().setItemFont(new Font("宋体", Font.PLAIN, 12));
		chart.getTitle().setFont(new Font("宋体", Font.PLAIN, 16));

		return chart;
	}

	public JFreeChart createBarChart(CategoryDataset dataset, Chart chartConfig) {
		JFreeChart chart = null;
		chart = ChartFactory.createBarChart(chartConfig.getTitle(),
				chartConfig.getxName(), chartConfig.getyName(), dataset,
				PlotOrientation.VERTICAL, true, true, false);

		CategoryPlot categoryplot = (CategoryPlot) chart.getPlot();

		NumberAxis numberaxis = (NumberAxis) categoryplot.getRangeAxis();
		numberaxis.setStandardTickUnits(NumberAxis.createIntegerTickUnits());
		BarRenderer barrenderer = (BarRenderer) categoryplot.getRenderer();
		barrenderer.setBaseItemLabelFont(new Font("宋体", Font.PLAIN, 12));
		barrenderer.setSeriesItemLabelFont(1, new Font("宋体", Font.PLAIN, 12));
		CategoryAxis domainAxis = categoryplot.getDomainAxis();

		// 设置距离图片左端距离
		domainAxis.setLowerMargin(0.03);
		// 设置距离图片右端距离
		domainAxis.setUpperMargin(0.02);
		// 设置 columnKey 是否间隔显示
		// domainAxis.setSkipCategoryLabelsToFit(true);
		categoryplot.setDomainAxis(domainAxis);

		// 设置最高的一个 Item 与图片顶端的距离
		numberaxis.setUpperMargin(0.2);

		// 设置X轴坐标上的文字
		domainAxis.setTickLabelFont(new Font("sans-serif", Font.PLAIN, 11));

		// 设置X轴的标题文字
		domainAxis.setLabelFont(new Font("宋体", Font.PLAIN, 12));

		// 设置Y轴坐标上的文字
		numberaxis.setTickLabelFont(new Font("sans-serif", Font.PLAIN, 12));

		// 设置Y轴的标题文字
		numberaxis.setLabelFont(new Font("黑体", Font.PLAIN, 12));

		// 解决底部汉字乱码
		chart.getLegend().setItemFont(new Font("宋体", Font.PLAIN, 12));
		chart.getTitle().setFont(new Font("宋体", Font.PLAIN, 16));

		return chart;

	}
	
	public JFreeChart createBar3DChart(CategoryDataset dataset, Chart chartConfig){
		JFreeChart chart = null ;
		chart = ChartFactory.createBarChart3D(chartConfig.getTitle(),
				chartConfig.getxName(), chartConfig.getyName() ,
				dataset, PlotOrientation.VERTICAL, true, true, true);

		CategoryPlot categoryplot = (CategoryPlot) chart.getPlot();
		
		
		categoryplot.setDomainGridlinesVisible(true);
		categoryplot.setRangeCrosshairVisible(true);
		categoryplot.setRangeCrosshairPaint(Color.blue);

		// 设置柱体的透明度 renderer渲染
		categoryplot.setForegroundAlpha(0.4f);

		BarRenderer3D renderer = new BarRenderer3D();
		renderer.setBaseOutlinePaint(Color.red);
		// 设置 Wall和背冲景 的颜色
		renderer.setWallPaint(Color.gray);
		categoryplot.setBackgroundPaint(Color.LIGHT_GRAY);
		// 设置每个分数段代表的柱的颜色
		renderer.setSeriesPaint(0, Color.blue);
		renderer.setSeriesPaint(1, new Color(0, 100, 255));
		renderer.setSeriesPaint(2, Color.GREEN);

		// 设置分数段代表的柱的 Outline 颜色
		renderer.setSeriesOutlinePaint(0, Color.black);
		renderer.setSeriesOutlinePaint(1, Color.BLACK);
		renderer.setSeriesOutlinePaint(2, Color.BLACK);

		// 设置阴影
		renderer.setShadowXOffset(1);
		renderer.setDefaultShadowsVisible(true);

		// 设置是否显示柱体的轮廓
		renderer.setDrawBarOutline(true);

		// 设置平行柱的之间距离
		renderer.setItemMargin(0.3);
		// 显示每个柱的数值，并修改该数值的字体属性

		renderer
				.setItemLabelGenerator(new StandardCategoryItemLabelGenerator());
		renderer.setItemLabelFont(new Font("黑体", Font.PLAIN, 12));
		renderer.setItemLabelsVisible(true);
		
		
		categoryplot.setRenderer(renderer);

		NumberAxis numberaxis = (NumberAxis) categoryplot.getRangeAxis();
		numberaxis.setStandardTickUnits(NumberAxis.createIntegerTickUnits());
		BarRenderer barrenderer = (BarRenderer) categoryplot.getRenderer();
		barrenderer.setBaseItemLabelFont(new Font("宋体", Font.PLAIN, 12));
		barrenderer.setSeriesItemLabelFont(1, new Font("宋体", Font.PLAIN, 12));
		CategoryAxis domainAxis = categoryplot.getDomainAxis();
		
		//设置距离图片左端距离
		domainAxis.setLowerMargin(0.03);
		//设置距离图片右端距离
		domainAxis.setUpperMargin(0.02);
		//设置 columnKey 是否间隔显示
//		domainAxis.setSkipCategoryLabelsToFit(true);
		categoryplot.setDomainAxis(domainAxis);
		
		// 设置最高的一个 Item 与图片顶端的距离
		numberaxis.setUpperMargin(0.2);

		// 设置X轴坐标上的文字
		domainAxis.setTickLabelFont(new Font("sans-serif", Font.PLAIN, 11));

		// 设置X轴的标题文字
		domainAxis.setLabelFont(new Font("宋体", Font.PLAIN, 12));

		// 设置Y轴坐标上的文字
		numberaxis.setTickLabelFont(new Font("sans-serif", Font.PLAIN, 12));

		// 设置Y轴的标题文字
		numberaxis.setLabelFont(new Font("黑体", Font.PLAIN, 12));

		// 解决底部汉字乱码
		chart.getLegend().setItemFont(new Font("宋体", Font.PLAIN, 12));
		chart.getTitle().setFont(new Font("宋体", Font.PLAIN, 16));
	
		return chart;
	}
	
	public JFreeChart createPieChart(CategoryDataset dataset, Chart chartConfig){
		JFreeChart chart = null ;
		DefaultPieDataset pieDataset = new DefaultPieDataset() ;
//		pieDataset.setValue("30以下", numberOfScoreStageDoubles[0]) ;
//		pieDataset.setValue("30-39", numberOfScoreStageDoubles[1]) ;
//		pieDataset.setValue("40-49", numberOfScoreStageDoubles[2]) ;
//		pieDataset.setValue("50-59", numberOfScoreStageDoubles[3]) ;
//		pieDataset.setValue("60-69", numberOfScoreStageDoubles[4]) ;
//		pieDataset.setValue("70-89", numberOfScoreStageDoubles[5]) ;
//		pieDataset.setValue("80-89", numberOfScoreStageDoubles[6]) ;
//		pieDataset.setValue("90以上", numberOfScoreStageDoubles[7]) ;
		
		
		chart = ChartFactory.createPieChart3D("成绩分布图", pieDataset, true, true, false) ;
		
		chart.setTitle(new TextTitle("成绩分布图",new Font("宋体",Font.PLAIN,12))) ;
		PiePlot pie = (PiePlot) chart.getPlot() ;
		pie.setLabelFont(new Font("黑体", Font.TRUETYPE_FONT, 12));
		pie.setBackgroundPaint(Color.white) ;
		//设置底部字体
		chart.getLegend().setItemFont(new Font("宋体",Font.PLAIN,12)) ;

//		获取类图
//		Plot categoryPlot = (CategoryPlot)chart.getPlot() ;
//		categoryPlot.setBackgroundPaint(Color.white) ;
		
	
		return chart;
	}

}
